package com.code.enums;

/**
 * 统一定义缓存KEY
 * 备注：
 * ① 枚举name应遵守以VALUE、LIST、SET、ZSET、HASH等开头
 * ② 枚举code应尽量简写形式，以工程主名字为开头，例如：whitecoin、cybermoney
 * ③ `:` 冒号分割的前后应该是一个名词词性，冒号前后是有上下级关系的，多个单词解释一个名词时，约定使用 `_`下划线分割
 * <p>
 * 举例：
 * ① WHITECOIN 的用户缓存 whitecoin:user:{userId}
 * ② WHITECOIN 的某用户地址信息缓存 whitecoin:user_address
 * <p>
 *
 * @author xiaoyaowang
 */
public enum CacheKeyEnum {

    /* ---------------用户相关缓存------------------ */

    /**
     * 验证码缓存，生存时长为1分钟
     */
    TELEGRAM_AUTH_CODE("%s", TimeEnum.ONE_MINUTES.sec()),

    /**
     * 验证码验证错误缓存，生存时长为1天
     */
    TELEGRAM_AUTH_CODE_FAILURE("%s:code_verify_failure", TimeEnum.ONE_DAY.sec()),

    /**
     * 验证码验证成功缓存，生存时长为1天
     */
    TELEGRAM_AUTH_CODE_SUCCESS("%s:code_verify_success", TimeEnum.ONE_DAY.sec()),

    /**
     * 验证码验证成功缓存，生存时长为1个月
     */
    TELEGRAM_RELEASE_ACCOUNT("release_account", TimeEnum.ONE_MONTH.sec()),

    /**
     * 设置同一个手机号一天的发送次数为10次
     */
    SMS_SEND_TIMES_ONE_DAY("sms_send_times_one_day:%s", TimeEnum.ONE_DAY.sec()),


    /**
     * 设置同一个手机号发送短信的间隔时间，生存时长为1分钟
     */
    SMS_SEND_INTERVAL("sms_send_interval:%s", TimeEnum.ONE_MINUTES.sec());

    /**
     * 缓存key
     */
    private final String code;

    /**
     * 过期时间（单位：秒）
     */
    private final Integer sec;

    CacheKeyEnum(String code, Integer sec) {
        this.code = code;
        this.sec = sec;
    }

    public String code() {
        return this.code;
    }

    public Integer sec() {
        return this.sec;
    }

    @Override
    public String toString() {
        return this.name();
    }

    /**
     * 格式化相关的key
     *
     * @param args 可变参数
     * @return 格式化后的key
     */
    public String formatKey(Object... args) {
        // 判断%s在this.code（缓存key）中的出现的次数
        int requiredNum = getSubStrCount(this.code, "%s");
        boolean isCorrectArgsNum = requiredNum != 0 && (null == args || args.length != requiredNum);
        if (isCorrectArgsNum) {
            throw new IllegalArgumentException("The number of parameters is not equal to the required number.");
        }
        return String.format(this.code, args);
    }

    /**
     * 子字符串出现的个数
     */
    public static int getSubStrCount(String str, String subStr) {
        int count = 0;
        int index = 0;
        while ((index = str.indexOf(subStr, index)) != -1) {
            index = index + subStr.length();
            count++;
        }
        return count;
    }

}
